<template>
  <a-modal
    v-model:open="openRef"
    title="编辑视频"
    centered
    width="416"
    :force-render="true"
    :mask-closable="false"
    @ok="handleOk"
    @cancel="onCancel"
  >
    <!-- 加载中 -->
    <div v-if="init" class="float-left text-center mt-30">
      <a-spin />
    </div>

    <!-- 表单 -->
    <div v-show="!init" class="float-left mt-24">
      <a-form
        ref="formRef"
        :model="formModel"
        :rules="rules"
        :label-col="{ span: 8 }"
        :wrapper-col="{ span: 16 }"
        @finish="onFinish"
      >
        <a-form-item
          label="视频分类"
          name="category_id"
          :rules="rules.category_id"
        >
          <a-tree-select
            v-model:value="formModel.category_id"
            :tree-data="categories"
            allow-clear
            tree-default-expand-all
            placeholder="视频分类"
            style="width: 200px"
            :tree-checkable="true"
          />
        </a-form-item>

        <a-form-item label="视频名称" name="name" :rules="rules.name">
          <a-input
            v-model:value="formModel.name"
            allow-clear
            placeholder="请输入视频名称"
            style="width: 200px"
          />
        </a-form-item>
      </a-form>
    </div>
  </a-modal>
</template>

<script setup lang="ts">
import { reactive, ref, watch } from "vue";
import { message } from "ant-design-vue";
import { resource, resourceCategory } from "@/api/index";

interface PropInterface {
  id: number;
  open: boolean;
  onCancel: () => void;
  onSuccess: () => void;
}

const props = defineProps<PropInterface>();

/**
 * openRef 用于 v-model:open（保持外部 prop 与内部状态同步）
 */
const openRef = ref(props.open);
watch(() => props.open, (val) => (openRef.value = val));

/** 表单 ref（指向 <a-form> 组件实例，可调用 validate/resetFields 等） */
const formRef = ref<any>(null);

/** 加载中标志 */
const init = ref(true);

/** 树形分类数据，注意：value/key 都要是字符串 */
const categories = ref<any[]>([]);

/** 表单数据：使用 reactive 对象（而不是 ref 对象） */
const formModel = reactive({
  name: "",
  // TreeSelect 在 tree-checkable 时 v-model 为数组 (string[])
  category_id: [] as string[] | null,
});

/** 表单校验规则 */
const rules = {
  name: [{ required: true, message: "请输入视频名称!" }],
  category_id: [{ required: true, message: "请选择视频分类!" }],
};

/** 点击模态框确认时：先校验 */
const handleOk = () => {
  // ant-design-vue 的表单实例上有 validate 方法
  formRef.value
    ?.validate?.()
    .then(() => {
      // 校验通过 -> 调用 onFinish（注意传入当前 model）
      onFinish({ ...formModel });
    })
    .catch((err: any) => {
      // 校验失败会进入这里
      console.log("表单校验失败", err);
    });
};

/** 监听弹窗打开和 id 变化，打开且 id 有效时加载数据 */
watch([() => props.id, openRef], ([id, openVal]) => {
  if (!openVal) return;
  init.value = true;
  // 拉分类（树）
  getCategory();
  // 拉详情（如果 id 有意义）
  if (props.id && props.id !== 0) {
    getDetail(props.id);
  } else {
    // 新开窗口且无 id
    formModel.name = "";
    formModel.category_id = [];
    init.value = false;
  }
});

/** 获取分类并构造 tree-data（注意转换 value/key 为字符串） */
const getCategory = async () => {
  try {
    const res: any = await resourceCategory.resourceCategoryList();
    const data = res.data.categories;
    if (JSON.stringify(data) !== "{}") {
      categories.value = buildTreeOptions(data, 0);
    } else {
      categories.value = [];
    }
  } catch (e) {
    console.error(e);
  }
};

/** 获取视频详情并回显（把后端 category_ids 转为 string[]） */
const getDetail = async (id: number) => {
  try {
    const res: any = await resource.videoDetail(id);
    const data = res.data.resources;
    formModel.name = data.name || "";
    // 后端返回 category_ids 可能是数组 -> 转成 string[]
    const catIds = res.data.category_ids;
    if (Array.isArray(catIds)) {
      formModel.category_id = catIds.map((n: number) => String(n));
    } else if (catIds === null || catIds === undefined) {
      formModel.category_id = [];
    } else {
      // 单值也转成数组字符串
      formModel.category_id = [String(catIds)];
    }
  } catch (e) {
    console.error(e);
  } finally {
    init.value = false;
  }
};

/** 构造 tree 节点：只返回 { title, value, key, children }，value/key 都用字符串 */
const buildTreeOptions = (departments: any, id: number) => {
  const arr: any[] = [];
  const list = departments[id] || [];
  for (let i = 0; i < list.length; i++) {
    const dep = list[i];
    const key = String(dep.id);
    if (!departments[dep.id]) {
      arr.push({ title: dep.name, value: key, key });
    } else {
      arr.push({
        title: dep.name,
        value: key,
        key,
        children: buildTreeOptions(departments, dep.id),
      });
    }
  }
  return arr;
};

/** 真正提交到后端（把 category_id 从 string[] -> number 或 单个 number） */
const onFinish = async (values: any) => {
  if (!values) return;
  // 防重复提交：这里用 init/另一个 flag 由你自己决定（简化处理）
  try {
    // 后端期望一个单一 category_id（参照你的 React 逻辑）
    let categoryId: number | null = 0;
    if (Array.isArray(values.category_id) && values.category_id.length > 0) {
      categoryId = Number(values.category_id[0]);
    } else if (typeof values.category_id === "string") {
      // 有时候可能是单字符串
      categoryId = Number(values.category_id);
    } else {
      categoryId = 0;
    }

    const payload = {
      name: values.name,
      category_id: categoryId,
    };

    await resource.videoUpdate(props.id, payload);
    message.success("保存成功！");
    props.onSuccess();
  } catch (e) {
    console.error(e);
  }
};
</script>

<style scoped>
.float-left {
  float: left;
}
.text-center {
  text-align: center;
}
.mt-24 {
  margin-top: 24px;
}
.mt-30 {
  margin-top: 30px;
}
</style>
